﻿// -------------------------------------------------------------------------------------------------------------------------------
// <copyright file="TestClearRow.cs" company="Exul">
//     Copyright (c) Exul. All rights reserved.
// </copyright>
// <author>
//     Exul
// </author>
// -------------------------------------------------------------------------------------------------------------------------------

namespace ExulLibrary.Mathematics.LinearAlgebra.Sequential.Tests.RMDenseMatrixTest
{
    #region Usings

    using System;
    using System.Diagnostics.CodeAnalysis;

    using ExulLibrary.Exceptions;

    using NUnit.Framework;

    #endregion

    /// <summary>
    ///     Test suite for <see cref="RMDenseMatrixExtensions.ClearRow{T}"/>.
    /// </summary>
    [TestFixture]
    [Category("ExulLibrary.Mathematics.LinearAlgebra.Sequential.RMDenseMatrixExtensions")]
    public sealed class TestClearRow
    {
        /// <summary>
        ///     Tests the method when row index is non-negative and less than rows count.
        /// </summary>
        /// <param name="rowIndex">
        ///     The index of the row.
        /// </param>
        [SuppressMessage(
            "Microsoft.Usage",
            "CA2233:OperationsShouldNotOverflow",
            MessageId = "rowIndex+1",
            Justification = "Division with remainder doesn't produce overflow")]
        [SuppressMessage(
            "Microsoft.Usage",
            "CA2233:OperationsShouldNotOverflow",
            MessageId = "rowIndex+2",
            Justification = "Division with remainder doesn't produce overflow.")]
        [Test]
        public void WhenRowIndexIsValid([Values(0, 1, 2)] int rowIndex)
        {
            // Arrange
            const int RowsCount = 3;
            var data = new[]
                       {
                           new[] { new object(), new object() },
                           new[] { new object(), new object() },
                           new[] { new object(), new object() }
                       };
            var instance = new RMDenseMatrix<object>(data);

            // Act
            instance.ClearRow(rowIndex);

            // Assert
            Assert.That(instance.Values[rowIndex][0], Is.Null);
            Assert.That(instance.Values[rowIndex][1], Is.Null);

            Assert.That(instance.Values[(rowIndex + 1) % RowsCount][0], Is.Not.Null);
            Assert.That(instance.Values[(rowIndex + 1) % RowsCount][1], Is.Not.Null);
            Assert.That(instance.Values[(rowIndex + 2) % RowsCount][0], Is.Not.Null);
            Assert.That(instance.Values[(rowIndex + 2) % RowsCount][1], Is.Not.Null);
        }

#if SAFE

        /// <summary>
        ///     Tests the method when row index is negative or greater than or equal to rows count.
        /// </summary>
        /// <param name="rowIndex">
        ///     The index of the row.
        /// </param>
        [Test]
        public void WhenRowIndexIsOutOfRange([Values(-1, 3)] int rowIndex)
        {
            // Arrange
            var data = new[]
                       {
                           new object[4],
                           new object[4],
                           new object[4]
                       };
            var instance = new RMDenseMatrix<object>(data);

            // Act and Assert
            Assert.That(
                () => instance.ClearRow(rowIndex),
                Throws.TypeOf<ElementIndexIsOutOfRangeException>().With.Property("ParamName").EqualTo("rowIndex"));
        }

        /// <summary>
        ///     Tests the method when matrix parameter is <see langword="null"/>.
        /// </summary>
        [Test]
        public void WhenMatrixIsNull()
        {
            // Act and Assert
            Assert.That(
                () => RMDenseMatrixExtensions.ClearRow<object>(null, 0),
                Throws.TypeOf<ArgumentNullException>().With.Property("ParamName").EqualTo("matrix"));
        }

#endif
    }
}